package flexo.file;

import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.ArrayList;

import flexo.common.LogMsgType;

/**
 * Creates files, handles local paths and retrieves full paths from those
 * local paths. 
 * @author Miguel
 */
public class FileSystem extends flexo.common.System
{
	public static final String ID = "file";
	
	protected ArrayList<String> pathList;
	
	/**
	 * Initializes the system and adds some default local paths.
	 */
	public FileSystem()
	{
		super(ID,flexo.common.System.UPDATE_NONE);
		flexo.Kernel.log("flexo.file.FileSytem", "Starting file system");
		pathList = new ArrayList<String>();		
		pathList.add("/");
		pathList.add("./");
		pathList.add("");
	}
	
	/**
	 * Adds a local path. Now you can access the file '/dir/file.txt'
	 * with the path 'file.txt'.
	 */
	public void addPath(String path)
	{
		if (!pathList.contains(path))
		{
			flexo.Kernel.log("flexo.file.FileSytem", "Adding path '"+path+"' to media directories");
			
			if (path.charAt(path.length()-1) != '/')
			{
				path = path + "/";
			}
			if (path.charAt(0) == '/')
			{
				path = path.substring(1);
			}
			pathList.add("/" + path);
			pathList.add("./" + path);
			pathList.add(path);
		}
	}
	
	/**
	 * @param relativePath the path of the file you want to open.
	 * @return a stream with the file specified.
	 */
	public InputStream getStream(String relativePath)
	{
		InputStream ret = null;
		
		ret = getClass().getClassLoader().getResourceAsStream(getFullPath(relativePath));
		
		return ret;
	}
	
	/**
	 * @param relativePath the path of the file you want to open.
	 * @return a BufferedReader with the file specified.
	 */
	public BufferedReader getBufferedReader(String relativePath)
	{
		BufferedReader ret = null;
		
		ret = new BufferedReader(new InputStreamReader(getStream(relativePath)));
		
		return ret;
	}
	
	/**
	 * @param relativePath the relative path of a file.
	 * @return the full path if the file is in a local path, otherwise returns null.
	 */
	public String getFullPath(String relativePath)
	{
		String ret = null;
		
		// We search until the path is found
		for (int i = 0; ret == null && i < pathList.size(); ++i)
		{
			ret = pathList.get(i) + relativePath;
			
			//melt.Melt.debugMsg("File.Manager","Checking " + ret);
			if (getClass().getClassLoader().getResourceAsStream(pathList.get(i) + relativePath) == null)
			{
				ret = null;
			}
		}
		
		if (ret == null)
		{
			flexo.Kernel.log("flexo.file.FileSytem","Couldn't find an absolute path for '" + relativePath + "'", LogMsgType.WARNING);
		}
		
		return ret;
	}
	
	/**
	 * Creates an empty file.
	 */
	public File createFile()
	{
		return new File();
	}
	
	/**
	 * Creates an empty file. Tries to find an existing file with
	 * the same name so that you can load it.
	 */
	public File createFile(String path)
	{
		return new File(getFullPath(path));
	}
}
